package fr.cie.blog.modeldao.hib;

import java.util.List;

import org.apache.log4j.Logger;
import org.hibernate.HibernateException;
import org.hibernate.Session;
import org.hibernate.Transaction;
import org.springframework.dao.DataAccessException;
import org.springframework.orm.hibernate3.support.HibernateDaoSupport;

import fr.cie.blog.beans.Article;
import fr.cie.blog.beans.Comment;
import fr.cie.blog.domainservice.IServiceArticle;

/**
 * @author AetM
 * 
 */
public class ArticleDaoImplHib extends HibernateDaoSupport implements
		IServiceArticle {
	/**
	 * Log4J the logger.
	 */
	private static final Logger LOG = Logger
			.getLogger(ArticleDaoImplHib.class);

	/*
	 * (non-Javadoc)
	 * 
	 * @see fr.cie.blog.domainservice.IServiceGeneric#save(java.lang.Object)
	 */
	@Override
	public final int save(final Article article) {
		final Session hibSession = getSessionFactory().getCurrentSession();
		final Transaction transaction = hibSession.beginTransaction();

		try {
			hibSession.saveOrUpdate(article);
			transaction.commit();

		} catch (DataAccessException e) {
			transaction.rollback();
			LOG.error("save Article error", e);

		} catch (HibernateException e) {
			transaction.rollback();
			LOG.error("save Article error", e);

		} finally {
			getSession().close();
		}
		return 1;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see fr.cie.blog.domainservice.IServiceGeneric#update(java.lang.Object)
	 */
	@Override
	public final int update(final Article article) {
		final Session hibSession = getSessionFactory().getCurrentSession();
		final Transaction transaction = hibSession.beginTransaction();

		try {
			hibSession.saveOrUpdate(article);
			transaction.commit();

		} catch (HibernateException e) {
			transaction.rollback();
			LOG.error("update Article error", e);

		} finally {
			getSession().close();
		}
		return 1;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see fr.cie.blog.domainservice.IServiceGeneric#delete(java.lang.Object)
	 */
	@Override
	public final int delete(final Article article) {
		final Session hibSession = getSessionFactory().getCurrentSession();
		final Transaction transaction = hibSession.beginTransaction();

		try {
			hibSession.delete(article);
			transaction.commit();

		} catch (HibernateException e) {
			transaction.rollback();
			LOG.error("delete Article error", e);

		} finally {
			getSession().close();
		}
		return 1;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see fr.cie.blog.domainservice.IServiceGeneric#findAll()
	 */
	@Override
	public final List<Article> findAll() {
		@SuppressWarnings("unchecked")
		final List<Article> list = (List<Article>) getHibernateTemplate()
				.find("from Article");
		return list;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * fr.cie.blog.domainservice.IServiceArticle#findByCategory(fr.cie.blog.
	 * beans.Category)
	 */
	@Override
	public final List<Article> findByCategory(final long categoryId) {
		@SuppressWarnings("unchecked")
		final List<Article> articleList = (List<Article>) getHibernateTemplate()
				.find("from Article as a where a.category.id = ?", categoryId);
		return articleList;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see
	 * fr.cie.blog.domainservice.IServiceArticle#findByComment(fr.cie.blog.beans
	 * .Comment)
	 */
	@Override
	public final Article findByComment(final Comment pComment) {
		final Article article = (Article) getHibernateTemplate().find(
				"from Article as a where a.id = ?",
				pComment.getArticleOwner().getId());
		return article;
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see fr.cie.blog.domainservice.IServiceGeneric#findById(int)
	 */
	@Override
	public final Article findById(final long pIdentifier) {
		return getHibernateTemplate().get(Article.class, pIdentifier);
	}

	/*
	 * (non-Javadoc)
	 * 
	 * @see fr.cie.blog.domainservice.IServiceArticle#get5lastArticles()
	 */
	@Override
	public final List<Article> findFiveLastArticles() {
		@SuppressWarnings("unchecked")
		final List<Article> articleList = (List<Article>) getHibernateTemplate()
				.find("from Article as a order by a.publicationDate");
		List<Article> resultList;
		if (articleList == null || articleList.size() < 5) {
			// list contains less than 5 articles.
			resultList = articleList;
		} else {
			// list contains more than 5 articles.
			resultList = articleList.subList(0, 4);
		}
		return resultList;
	}
}